package com.org.core.servlet;

import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.org.core.constant.CommonConstant;
import com.org.core.constant.ReturnTemp;
import com.org.core.container.CommonContainer;
import com.org.core.interfaces.CommonController;
import com.org.core.utils.BeansUtil;

public class DispatcherServlet extends HttpServlet {
    private static final long serialVersionUID = 1L;
	private static Log log = LogFactory.getLog(DispatcherServlet.class);
	private static Map<String, Method> mtdContainer = new HashMap<String, Method>();
	private static final Pattern PATTERN = Pattern.compile("/([a-zA-Z]+)+");
	
	public DispatcherServlet() {
		super();
	}
	
	public void init() throws ServletException {
		// Put your code here
	}
	public void doGet(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doPost(request, response);
	}

	public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String _servletName ="";
			/* 0. 设置数据部缓存  */
			response.setHeader("Pragma","no-cache"); 
			response.setHeader("Cache-Control","no-cache"); 
			response.setDateHeader("Expires", 0); 
			
			if(request.getSession().getAttribute(CommonConstant.SERVLET) == null){
				request.getSession().setAttribute(CommonConstant.SERVLET, this);
			}

			if(StringUtils.isNotEmpty(request.getContextPath()) && !!CommonContainer.containsKey(request.getContextPath())) {
				CommonContainer.saveData(CommonConstant.FIXED_PATH, request.getContextPath());
			}
			
//			System.out.println("request.getContextPath()  "+request.getContextPath()); // /bbs
//			System.out.println("request.getServletPath()  "+request.getServletPath()); // /user.do /user/login.do
//			System.out.println("request.getPathInfo()  "+request.getPathInfo());
			
			String pathInfo = request.getServletPath();
			Matcher match = PATTERN.matcher(pathInfo);
			List<String> pathtemp = new ArrayList<String>();
			while(match.find()) {
				pathtemp.add(match.group(1));
			}
			String servletName = "";
			String mtdName = "";
			
			if(pathtemp.size() == 1) {
				servletName = pathtemp.get(0);
			}
			if(pathtemp.size() > 1) {
				servletName = pathtemp.get(0);
				mtdName = pathtemp.get(1);
			}
			
			servletName += "Controller";
			
			// Controller从spring容器中取得
			CommonController aim = (CommonController)BeansUtil.getBean(servletName);
			if(aim == null) {
				throw new RuntimeException("不存在Controller: "+ servletName);
			}
			
			/*****判断是否为重复提交************************ 
			 * 可使用 用户唯一身份+时间作为唯一号
			String token = request.getParameter("token");
			if(token!=null){
				HttpSession session=request.getSession();
				synchronized(session){
					Object value=session.getAttribute(servletName);
					if(value!=null){
						//重复提交请求，直接驳回
						return ;
					}
					session.setAttribute(servletName, UUID.randomUUID());
				}
				String tokenParam=request.getSession().getAttribute("token")==null?"":request.getSession().getAttribute("tokenParam").toString();
				
				if(token.equals(tokenParam)){
					request.getSession().removeAttribute("token");
				}else{
					return;
				}
			}
			*/
			
			/*******************************************/
			if(StringUtils.isEmpty(mtdName)){
				aim.post(request, response);
			} else {
				Method m = null;
				String mtdKey = servletName + mtdName;
				if(mtdContainer.containsKey(mtdKey)) {
					m = mtdContainer.get(mtdKey);
				} else {
					try {
						m = aim.getClass().getDeclaredMethod(mtdName, new Class<?>[]{HttpServletRequest.class, HttpServletResponse.class});
						mtdContainer.put(mtdKey, m);
					} catch (SecurityException e) {
						ReturnTemp temp = new ReturnTemp("SYS001", "系统异常:"+e.getMessage());
						throw new RuntimeException(temp.toString());
					} catch (NoSuchMethodException e) {
						ReturnTemp temp = new ReturnTemp("SYS002", "系统异常:"+e.getMessage());
						throw new RuntimeException(temp.toString());
					}
				}
				
				if(m != null) {
					try {
						m.invoke(aim, request, response);
					} catch (IllegalArgumentException|IllegalAccessException|InvocationTargetException e) {
						throw new RuntimeException("系统异常:"+e.getMessage());
					}
				}
			}
			log.debug("DispatcherServlet-->" + _servletName);
	}
	
	public void redirect(String targetUrl,HttpServletResponse response) throws Exception{
		response.sendRedirect(targetUrl);
	}

	public void destroy() {
	}
}
